from fabric import Connection
import os
import logging
import hashlib

logging.basicConfig(level=logging.INFO,  # 控制台打印的日志级别
                    # filename=filename,
                    # filemode='a',  # 模式，有w和a，w就是写模式，每次都会重新写日志，覆盖之前的日志
                    format='%(asctime)s - %(pathname)s[line:%(lineno)d] - %(levelname)s: %(message)s'
                    )
logger = logging.getLogger(__name__)


class MyFab:

    def __init__(self, host="pi@192.168.1.150", password="raspberry", local_path="", remote_path="/home/pi/fsc-system"):
        self.host = host
        self.password = password
        self.local_path = local_path
        self.remote_path = remote_path
        self.timer_start = False
        self.timer_cnt = 0

        logger.info("host: %s" % self.host)
        logger.info("password: %s" % self.password)
        logger.info("local_path: %s" % self.local_path)
        logger.info("remote_path: %s" % self.remote_path)

    def connect(self):
        try:
            self.timer_cnt = 0
            self.timer_start = True
            self.conn = Connection(host=self.host, connect_kwargs={"password": self.password})
            self.conn.open()
            logger.info(self.conn.is_connected)
        except Exception as e:
            logger.info(e)

    def is_connected(self):
        return self.conn.is_connected

    def run_ls(self):
        self.conn.run("ls")

    def upgrade_web(self):
        print("upgrade web start...")
        local_file = "{0}\\{1}".format(self.local_path, 'web.zip')
        remote_file = "{0}\\{1}".format(self.remote_path, 'web.zip')
        logger.info("put file: %s -> %s" % (local_file, remote_file))
        # 上传文件
        self.conn.put(local_file, self.remote_path)
        with self.conn.cd(self.remote_path):
            self.conn.run('ls')
            self.conn.run('sudo docker-compose stop web')
            # 解压并覆盖
            self.conn.run('unzip -o web.zip')
            # self.conn.run('rm web.zip')
            # 重新编译镜像
            # # run('sudo docker-compose build web')
            # 重启web服务
            self.conn.run('sudo docker-compose up -d web')
            # 清除所有None镜像
            # run('sudo docker rmi $(sudo docker images -q -f dangling=true)')
        return True

    def upgrade_server(self):
        logger.info("upgrade server start...")
        local_file = "{0}\\{1}".format(self.local_path, 'server.zip')
        remote_file = "{0}\\{1}".format(self.remote_path, 'server.zip')
        logger.info("put file: %s -> %s" % (local_file, remote_file))
        # 上传文件
        self.conn.put(local_file, self.remote_path)
        with self.conn.cd(self.remote_path):
            self.conn.run('sudo docker-compose stop server')
            self.conn.run('unzip -o server.zip')
            self.conn.run('rm server.zip')
            self.conn.run('sudo docker-compose build server')
            self.conn.run('sudo docker-compose up -d server')
            self.conn.run('sudo docker rmi $(sudo docker images -q -f dangling=true)')

    def upgrade_emqx(self):
        logger.info("upgrade emqx start...")
        local_file = "{0}\\{1}".format(self.local_path, 'emqx.zip')
        remote_file = "{0}\\{1}".format(self.remote_path, 'emqx.zip')
        logger.info("put file: %s -> %s" % (local_file, remote_file))
        self.conn.put(local_file, self.remote_path)
        with self.conn.cd(self.remote_path):
            self.conn.run('sudo docker-compose stop emqx')
            self.conn.run('unzip -o emqx.zip')
            self.conn.run('rm emqx.zip')
            self.conn.run('sudo docker-compose build emqx')
            self.conn.run('sudo docker-compose up -d emqx')

    def upgrade_mysql(self):
        logger.info("upgrade emqx start...")
        local_file = "{0}\\{1}".format(self.local_path, 'mysql.zip')
        remote_file = "{0}\\{1}".format(self.remote_path, 'mysql.zip')
        logger.info("put file: %s -> %s" % (local_file, remote_file))
        self.conn.put(local_file, self.remote_path)
        with self.conn.cd(self.remote_path):
            self.conn.run('sudo docker-compose stop mysqldb')
            self.conn.run('unzip -o mysql.zip')
            self.conn.run('rm mysql.zip')
            self.conn.run('sudo docker-compose build mysqldb')
            self.conn.run('sudo docker-compose up -d mysqldb')

    def upgrade_docker(self):
        logger.info("upgrade emqx start...")
        local_file = "{0}\\{1}".format(self.local_path, 'docker-compose.yml')
        remote_file = "{0}\\{1}".format(self.remote_path, 'docker-compose.yml')
        logger.info("put file: %s -> %s" % (local_file, remote_file))
        self.conn.put(local_file, self.remote_path)
        with self.conn.cd(self.remote_path):
            self.conn.run('sudo docker-compose stop')
            self.conn.run('sudo docker-compose up -d')
            # run('sudo docker rmi $(sudo docker images -q -f dangling=true)')

    def upgrade_all(self):
        self.upgrade_web()
        self.upgrade_server()

    def put_task(self, local_path: str, remote_path: str):                 # 上传文件任务函数
        self.conn.put(local_path, remote_path)

    def get_remote_file_md5(self, remote_path: str):            #校验文件任务函数
        # with settings(warn_only=True):
        #     #本地local命令需要配置capture=True才能捕获返回值
        #     lmd5=local("md5sum /data/test.tar.gz",capture=True).split(' ')[0]
        rmd5 = self.conn.run("md5sum %s" % remote_path).split(' ')[0]
        print(rmd5)

    # 计算本地文件md5码
    def get_file_md5(self, filename):
        logger.info(filename)
        if not os.path.isfile(filename):
            return
        myhash = hashlib.md5()
        f = open(filename, 'rb')
        while True:
            b = f.read(8096)
            if not b:
                break
            myhash.update(b)
        f.close()
        return myhash.hexdigest()


if __name__ == '__main__':
    f = MyFab(host='pi@192.168.1.150', password="raspberry", local_path=os.getcwd()+'\\dist\\fsc-rpi4-v2.0.0', remote_path="/home/pi/fsc-system")
    # f.upgrade_web()
    # f.upgrade_emqx()